home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
System Booster
/
System Booster.iso
/
Systemmonitors
/
RSys
/
RSysSrc.lha
/
RSysFiletype.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-09-19
|
10KB
|
499 lines
/*
***************************************************************************
*
* Datei:
* RSysFiletype.c
*
* Inhalt:
*
* --- Globale Routinen ---
*
* int filetype ( char *Name );
*
* --- Lokale Routinen ---
*
* static int IsDirectory ( char *Name );
* static UBYTE Local2Upper ( UBYTE c );
* static UBYTE StrCmp ( char *a , char *b );
*
* Bemerkungen:
* Routinen zur Ermittlung des Typs einer Datei.
*
* Erstellungsdatum:
* 07-Jul-93 Rolf Böhme
*
* Änderungen:
* 07-Jul-93 Rolf Böhme Erstellung
*
***************************************************************************
*/
#include "RSys.h"
/*
* Die Routinen zur Überprüfung von Filetypen wurden komplett aus
* dem Terminalprogramm TERM von Olaf 'Olsen' Barthel entnommen. Ich
* habe ein paar Teile modifiziert und die Kommentare beibehalten.
* Faulheit overwhelmed me...;-)
*/
int global_type;
char *mess[]=
{
"Disk/Directory",
"File",
"Icon file",
"Text file",
"C Sourcefile",
".h-C-Include",
"Assembler file",
"Assembler-Include file",
".MOD file",
"ARexx program",
"BASIC program",
"TeX file",
"MetaFONT file",
"GF file",
"TeX-Font file",
"TeX-DVI file",
"Font library",
"MANX Objectfile (V3.x)",
"MANX Objectfile (V5.x)",
"MANX Libraryfile (V3.x)",
"MANX Libraryfile (V5.x)",
"Objekt file",
".LIB file (Object library)",
"Executable",
"Library",
"Device",
"Filesystem",
"Handler",
"GIF picture",
"ILBM graphic",
"Animation",
"8SVX song",
"SMUS-Song",
"FTXT format",
"Preferences",
"Term file",
"Imploder file",
"Powerpacker file",
"Arc archive",
"LHArc archive",
"Zoo archive",
"ZIP archive",
"DMS archive",
"WARP archive",
"ZOOM archive",
"WordPerfect document"
};
struct Suffix
{
char *Name;
UBYTE Type;
};
/*
* Some file name suffixes for text files and the approriate file types.
*/
struct Suffix TextSuffix[]=
{
".C", TYPE_C,
".CP", TYPE_C,
".CC", TYPE_C,
".H", TYPE_H,
".ASM", TYPE_ASM,
".A", TYPE_ASM,
".S", TYPE_ASM,
".I", TYPE_I,
".BAS", TYPE_BASIC,
".GFA", TYPE_BASIC,
".REXX", TYPE_REXX,
".CED", TYPE_REXX,
".VLT", TYPE_REXX,
".CPR", TYPE_REXX,
".TxEd", TYPE_REXX,
".TEX", TYPE_TEX,
".STY", TYPE_TEX,
".MF", TYPE_METAFONT,
".MOD", TYPE_MOD,
".DEF", TYPE_MOD,
".WP", TYPE_WORDPERFECT
};
/*
* Some more file name suffixes for executable files and the approriate
* file types.
*/
struct Suffix ExecutableSuffix[]=
{
".device", TYPE_DEVICE,
".library", TYPE_LIBRARY,
"FileSystem", TYPE_FILESYS,
"Handler", TYPE_HANDLER
};
/*
* Local2Upper(UBYTE c):
*
* Custom version of toupper, will also handle international characters.
*/
static UBYTE
Local2Upper(UBYTE c)
{
return ((UBYTE) ((((c) >= 224 && (c) <= 254) || ((c) >= 'a' && (c) <= 'z')) ? (c) - 32 : c));
}
/*
* StrCmp(UBYTE *a,UBYTE *b):
*
* Custom version of strcmp, compares ignoring case.
*/
static UBYTE
StrCmp(char *a, char *b)
{
for (; Local2Upper((UBYTE) * a) == Local2Upper((UBYTE) * b); a++, b++)
{
if (!(*a)) return (0);
}
return ((UBYTE) (Local2Upper((UBYTE) * a) - Local2Upper((UBYTE) * b)));
}
static int
IsDirectory(char *Name)
{
struct FileInfoBlock *FileInfo;
int isdir = FALSE;
DPOS;
if (NOT(exist(Name))) return FALSE;
if (FileInfo = (struct FileInfoBlock *) AllocDosObject(DOS_FIB, TAG_DONE))
{
BPTR FileLock;
if (FileLock = Lock((UBYTE *) Name, ACCESS_READ))
{
if (Examine(FileLock, FileInfo)) isdir = (FileInfo->fib_DirEntryType > 0) ? TRUE : FALSE;
UnLock(FileLock);
}
FreeDosObject(DOS_FIB, FileInfo);
}
return isdir;
}
int
filetype(char *Name)
{
/* A table of valid ASCII characters (7 bits). */
BYTE ValidTab[256] =
{
0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0,
0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
};
/* A table of clearly invalid ASCII characters (8 bits). */
BYTE InvalidTab[256] =
{
1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1,
1, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
};
ULONG *Buffer;
int Type = TYPE_FILE;
SHORT i,
Len = strlen(Name);
DPOS;
/*
* Allocate a buffer for the first 400 bytes of the file.
*/
if(IsDirectory(Name)) return TYPE_DIR;
if (Buffer = (ULONG *) MyAllocVec(400, MEMF_CLEAR, NO_KILL))
{
BPTR File,
Size;
/* Open the file. */
if (File = Open((UBYTE *) Name, MODE_OLDFILE))
{
/* Read the first 400 bytes. */
if ((Size = Read(File, (char *)Buffer, 400)) >= sizeof(ULONG))
{
/* Examine the first longword. */
switch (Buffer[0])
{
case 0x03E7:
Type = TYPE_OBJECT;
break;
case 0x03F3:
Type = TYPE_EXECUTABLE;
break;
case 0x03FA:
Type = TYPE_LIB;
break;
case 0xF7593647:
Type = TYPE_TEXFONT;
break;
case 0xF7020183:
Type = TYPE_TEXDVI;
break;
case 0xF7832020:
Type = TYPE_GF;
break;
case 'FLIB':
Type = TYPE_FLIB;
break;
case 'FORM':
switch (Buffer[2])
{
case 'ILBM':
Type = TYPE_ILBM;
break;
case 'ANIM':
Type = TYPE_ANIM;
break;
case '8SVX':
Type = TYPE_8SVX;
break;
case 'SMUS':
Type = TYPE_SMUS;
break;
case 'FTXT':
Type = TYPE_FTXT;
break;
case 'PREF':
Type = TYPE_PREFS;
break;
case 'TERM':
Type = TYPE_TERM;
break;
}
break;
case 'IMP!':
Type = TYPE_IMPLODER;
break;
case 'PP20':
Type = TYPE_POWERPACKER;
break;
case 'DMS!':
Type = TYPE_DMS;
break;
case 'Warp':
Type = TYPE_WARP;
break;
case 'ZOOM':
Type = TYPE_ZOOM;
break;
case 0x504B0304:
Type = TYPE_ZIP;
break;
case 'ZOO ':
Type = TYPE_ZOO;
break;
case 'GIF8':
Type = TYPE_GIF;
break;
default:
break;
}
/*
* No match yet, see if it's an ASCII file.
*/
if (Type == TYPE_FILE)
{
UBYTE *CharBuffer = (UBYTE *) Buffer;
SHORT Count = 0;
for (i = 0; i < Size; i++)
{
if (ValidTab[CharBuffer[i]]) Count++;
else
{
if (InvalidTab[CharBuffer[i]])
{
Count = 0;
break;
}
}
}
/*
* If more than 75% of the characters in the first 400 bytes
* are legal ASCII characters this file is supposed to be a
* text file.
*/
if (Count > 3 * (Size / 4)) Type = TYPE_TEXT;
}
/* Still no match, have another try */
if (Type == TYPE_FILE)
{
if ((Buffer[0] & 0xFFFF0000) == 0x1A080000) Type = TYPE_ARC;
else
{
if ((Buffer[0] & 0x0000FFFF) == 0x00002D6C && (Buffer[1] & 0xFF00FF00) == 0x68002D00)
Type = TYPE_LHARC;
else
{
switch (Buffer[0] & 0xFFFF0000)
{
case 0x434A0000:
Type = TYPE_NEWMANX;
break;
case 0x414A0000:
Type = TYPE_OLDMANX;
break;
case 0x636A0000:
Type = TYPE_NEWMANXLIB;
break;
case 0x616A0000:
Type = TYPE_OLDMANXLIB;
break;
case 0xF5000000:
Type = TYPE_BASIC;
break;
default:
break;
}
}
}
}
/*
* Take a look at the file name suffixes.
*/
global_type = Type;
switch (Type)
{
case TYPE_TEXT:
for (i = 0; i < sizeof(TextSuffix) / sizeof(struct Suffix); i++)
{
Size = strlen(TextSuffix[i].Name);
if (Len >= Size)
{
if (!StrCmp(&Name[Len - Size], TextSuffix[i].Name))
{
Type = TextSuffix[i].Type;
break;
}
}
}
break;
case TYPE_EXECUTABLE:
for (i = 0; i < sizeof(ExecutableSuffix) / sizeof(struct Suffix); i++)
{
Size = strlen(ExecutableSuffix[i].Name);
if (Len >= Size)
{
if (!StrCmp(&Name[Len - Size], ExecutableSuffix[i].Name))
{
Type = ExecutableSuffix[i].Type;
break;
}
}
}
break;
case TYPE_OBJECT:
if (Len >= 4)
if (!StrCmp(&Name[Len - 4], ".LIB")) Type = TYPE_LIB;
break;
default:
break;
}
}
Close(File);
}
MyFreeVec(Buffer);
}
return Type;
}